﻿using System;
using System.Data;
using System.Configuration;
using System.Linq;
using System.Web;
using System.Web.Security;
using System.Web.UI;
using System.Web.UI.HtmlControls;
using System.Web.UI.WebControls;
using System.Web.UI.WebControls.WebParts;
using System.Xml.Linq;
using HRProject.Code.DTO;
using System.Collections.Generic;

namespace HRProject.Code.DAO
{
    public class TaskTypeDAO : BaseDAO
    {
        public TaskTypeDAO()
            : base ()
        {
        }

        public BLTaskType getRootTaskType()
        {
            List<BLTaskType> taskTypes = select();
            BLTaskType root = arrangeTaskType(taskTypes);
            return root;
        }

        private List<BLTaskType> select()
        {
            List<BLTaskType> result = new List<BLTaskType>();
            List<BaseCondition> condition = new List<BaseCondition>();
            condition.Add(new BaseCondition("@id", Guid.Empty, ParameterDirection.Input));
            condition.Add(new BaseCondition("@name", string.Empty, ParameterDirection.Input));
            condition.Add(new BaseCondition("@parentId", Guid.Empty, ParameterDirection.Input));
            DataTable data = select("usp_searchTaskTypes", condition);
            for (int i = 0; i < data.Rows.Count; i++)
            {
                BLTaskType taskType = new BLTaskType();
                taskType.Id = (Guid)data.Rows[i]["TaskTypeId"];
                taskType.Name = (string)data.Rows[i]["TaskTypeName"];
                taskType.Description = (string)data.Rows[i]["Description"];
                taskType.Parent = new BLTaskType();
                taskType.Parent.Id = (Guid)data.Rows[i]["ParentTaskTypeId"];
                taskType.Parent.Name = (string)data.Rows[i]["ParentTaskTypeName"];
                taskType.DataSignature = (long)data.Rows[i]["DataSignature"];
                taskType.CreateDate = (DateTime)data.Rows[i]["CreateDate"];
                taskType.CreateUserId = (Guid)data.Rows[i]["CreateUserId"];
                taskType.UpdateDate = (DateTime)data.Rows[i]["UpdateDate"];
                taskType.UpdateUserId = (Guid)data.Rows[i]["UpdateUserId"];
                result.Add(taskType);
            }
            return result;
        }

        public List<BLTaskType> search(BLTaskType filter)
        {
            List<BLTaskType> result = new List<BLTaskType>();
            List<BaseCondition> condition = new List<BaseCondition>();
            condition.Add(new BaseCondition("@id", filter.Id,ParameterDirection.Input));
            condition.Add(new BaseCondition("@name", filter.Name,ParameterDirection.Input));
            condition.Add(new BaseCondition("@parentId", filter.Parent.Id,ParameterDirection.Input));
            DataTable data = select("usp_searchTaskTypes", condition);
            for (int i = 0; i < data.Rows.Count; i++)
            {
                BLTaskType taskType = new BLTaskType();
                taskType.Id = (Guid)data.Rows[i]["TaskTypeId"];
                taskType.Name = (string)data.Rows[i]["TaskTypeName"];
                taskType.Description = (string)data.Rows[i]["Description"];
                taskType.Parent = new BLTaskType();
                taskType.Parent.Id = (Guid)data.Rows[i]["ParentTaskTypeId"];
                taskType.Parent.Name = (string)data.Rows[i]["ParentTaskTypeName"];
                taskType.DataSignature = (long)data.Rows[i]["DataSignature"];
                taskType.CreateDate = (DateTime)data.Rows[i]["CreateDate"];
                taskType.CreateUserId = (Guid)data.Rows[i]["CreateUserId"];
                taskType.UpdateDate = (DateTime)data.Rows[i]["UpdateDate"];
                taskType.UpdateUserId = (Guid)data.Rows[i]["UpdateUserId"];
                result.Add(taskType);
            }
            return result;
        }

        private BLTaskType arrangeTaskType(List<BLTaskType> taskTypes)
        {
            BLTaskType result = new BLTaskType();
            result.Name = "General";
            foreach (BLTaskType taskType in taskTypes)
            {
                bind(result, taskType);
            }
            return result;
        }

        private bool bind(BLTaskType ancestor, BLTaskType taskType)
        {
            if (ancestor.Id == taskType.Parent.Id)
            {
                int index = 0;
                for (int i = 0; i < ancestor.Children.Count; i++)
                {
                    if (taskType.Name.ToLower().CompareTo(ancestor.Children[i].Name.ToLower()) > 0)
                    {
                        index = i+1;
                        break;
                    }
                }
                ancestor.Children.Insert(index, taskType);
                taskType.Parent = ancestor;
                return true;
            }
            foreach (BLTaskType child in ancestor.Children)
            {
                if (bind(child, taskType))
                {
                    return true;
                }
            }
            return false;
        }

        public int insert(BLTaskType taskType)
        {
            List<BaseCondition> condition = new List<BaseCondition>();
            int errorCode = 0;
            condition.Add(new BaseCondition("@id", Guid.NewGuid(), ParameterDirection.Input));
            condition.Add(new BaseCondition("@name",taskType.Name,ParameterDirection.Input));
            condition.Add(new BaseCondition("@description", taskType.Description, ParameterDirection.Input));
            condition.Add(new BaseCondition("@parentId", taskType.Parent.Id, ParameterDirection.Input));
            condition.Add(new BaseCondition("@createUserId", Membership.GetUser().ProviderUserKey.ToString(),ParameterDirection.Input));
            condition.Add(new BaseCondition("@dataSignature",taskType.DataSignature,ParameterDirection.Input));
            condition.Add(new BaseCondition("@errorCode",errorCode,ParameterDirection.Output));
            int result = update("usp_addTaskType", condition);
            return result;
        }

        public int update(BLTaskType taskType)
        {
            List<BaseCondition> condition = new List<BaseCondition>();
            int errorCode = 0;
            condition.Add(new BaseCondition("@id", taskType.Id, ParameterDirection.Input));
            condition.Add(new BaseCondition("@name", taskType.Name, ParameterDirection.Input));
            condition.Add(new BaseCondition("@description", taskType.Description, ParameterDirection.Input));
            condition.Add(new BaseCondition("@updateUserId", Membership.GetUser().ProviderUserKey.ToString(), ParameterDirection.Input));
            condition.Add(new BaseCondition("@dataSignature", taskType.DataSignature, ParameterDirection.Input));
            condition.Add(new BaseCondition("@errorCode", errorCode, ParameterDirection.Output));
            int result = update("usp_updateTaskType", condition);
            return result;
        }

        public int delete(BLTaskType taskType)
        {
            List<BaseCondition> condition = new List<BaseCondition>();
            int errorCode = 0;
            condition.Add(new BaseCondition("@id", taskType.Id, ParameterDirection.Input));
            condition.Add(new BaseCondition("@updateUserId", Membership.GetUser().ProviderUserKey.ToString(), ParameterDirection.Input));
            condition.Add(new BaseCondition("@dataSignature", taskType.DataSignature, ParameterDirection.Input));
            condition.Add(new BaseCondition("@errorCode", errorCode, ParameterDirection.Output));
            int result = update("usp_deleteTaskType", condition);
            return result;
        }
    }
}
